import mongodbHandle from '../handle/mongodbHandle'
import * as moment from 'moment'
import app from '../app'
import utils from '../core/utils'
import redisHandle from './redisHandle'
import * as schedule from 'node-schedule'
import * as cluster from 'cluster'

var ObjectId = require('mongodb').ObjectId;
var bossExpireTime = 33 * 60
var bossRewardTime = 5 * 60

var worldBossReward = [
    [[170010, 10], [170004, 8]],
    [[170010, 8], [170004, 5]],
    [[170010, 5], [170004, 3]],
    [[170010, 1], [170004, 1]]
]
var treasureReward = [173001, 173002, 173003, 173004, 173005, 173006, 173007, 173008, 173009, 173010, 173011, 173012, 173013, 173014, 173015, 173016]
class WorldBossHandle {

    schedule = async () => {
        // schedule.scheduleJob('0 0/2 * * * *', async () => {
        //     console.log('世界boss结算')
        //     await this.worldBossReward()
        // });
    }

    // 奇遇boss
    worldBossEvent = async (serverID, pid) => {
        let nowTime = new Date().getTime()
        let key = `wb_${serverID}`
        let eventJson = await redisHandle.get(key)
        if (eventJson) {
            let event = JSON.parse(eventJson)
            if (nowTime - event.createTime < 60 * 1000) {
                return {
                    event: {}
                }
            }
            let doc = await mongodbHandle.playerDao.findOne({ _id: ObjectId(event.userId) })
            event.userName = doc ? doc.playerData.playerName : '幸运女神'
            event.expireTime = event.createTime + (bossExpireTime - 180) * 1000
            event.bossMap = 100303
            return {
                event
            }
        } else {
            let trigger = Math.random() * 1000
            if (trigger >= 470 && trigger <= 500) {
                // if (trigger >= 0) {
                let myData = await mongodbHandle.playerDao.findOne({ _id: ObjectId(pid) })
                let event = {
                    eventId: utils.randomString(8) + moment().millisecond(),
                    userId: pid,
                    userName: myData.playerData.playerName,
                    createTime: nowTime,
                    bossMap: utils.getOneFromArray([100303]),
                }
                await redisHandle.set(key, JSON.stringify(event))
                await redisHandle.expire(key, bossExpireTime)
                return {
                    event: event
                }
            } else {
                return {
                    event: {}
                }
            }
        }
    }

    // 记录伤害
    battleWorldBoss = async (serverID, eventId, pid, damage) => {
        let nowTime = new Date().getTime()
        let key = `wb_${serverID}`
        let eventJson = await redisHandle.get(key)
        let totalDamage = damage
        if (eventJson) {
            let event = JSON.parse(eventJson)
            if (event.eventId !== eventId) {
                return {
                    status: -1 // boss已经消失 
                }
            }
            // 伤害
            let key2 = `${key}_${eventId}_player_${pid}_damage`
            await redisHandle.increaseBy(key2, damage)
            await redisHandle.expire(key2, bossExpireTime + bossRewardTime)
            // 次数
            let key3 = `${key}_${eventId}_player_${pid}_times`
            await redisHandle.increaseBy(key3, 1)
            await redisHandle.expire(key3, bossExpireTime + bossRewardTime)
            let beforeDamage = await redisHandle.get(key2) || 0
            totalDamage += Number(beforeDamage)
        }
        return {
            totalDamage
        }
    }

    // 伤害排行
    worldBossRank = async (serverID, eventId, pid) => {
        let key = `wb_${serverID}`
        let eventJson = await redisHandle.get(key)
        let rank = []
        if (eventJson) {
            let event = JSON.parse(eventJson)
            if (event.eventId !== eventId) {
                return {
                    status: -1 // boss已经消失 
                }
            }
            let nowTime = new Date().getTime()
            // 判断boss是否到消失时间
            if (nowTime - event.createTime < (bossExpireTime - 150) * 1000) {
                let key2 = `${key}_${event.eventId}_*_damage`
                let allDamage: any = await redisHandle.getAll(key2) || []
                for (let i = 0; i < allDamage.length; i++) {
                    let key3 = allDamage[i];
                    let damage = await redisHandle.get(key3)
                    var matchReg = /(?<=player_).*?(?=_damage)/
                    let pid = key3.match(matchReg)
                    if (pid && pid[0]) {
                        let doc = await mongodbHandle.playerDao.findOne({ _id: ObjectId(pid[0]) })
                        if (doc) {
                            rank.push({ userId: pid[0], damage, username: doc.playerData.playerName })
                        }
                    }
                }
            }
        }
        rank = rank.sort((a, b) => {
            return b.damage - a.damage
        })
        // 次数
        let key3 = `${key}_${eventId}_player_${pid}_times`
        let times = await redisHandle.get(key3) || 0
        return {
            times,
            rank
        }
    }

    // 结算
    worldBossReward = async () => {
        let nowTime = new Date().getTime()
        let serverList = await mongodbHandle.serverDao.find({})
        for (let i = 0; i < serverList.length; i++) {
            let doc = serverList[i];
            let key = `wb_${doc.newServerID}`
            let eventJson = await redisHandle.get(key)
            console.log('世界boss事件_' + doc.newServerID, eventJson)
            if (eventJson) {
                let event = JSON.parse(eventJson)
                // 判断boss是否到消失时间
                if (nowTime - event.createTime >= (bossExpireTime - 120) * 1000) {
                    let rank = []
                    let key2 = `${key}_${event.eventId}_*_damage`
                    let allDamage: any = await redisHandle.getAll(key2)
                    console.log("满足世界boss结算条件-服务器" + doc.newServerID)
                    for (let i = 0; i < allDamage.length; i++) {
                        let key3 = allDamage[i];
                        let damage = await redisHandle.get(key3)
                        var matchReg = /(?<=player_).*?(?=_damage)/
                        let pid = key3.match(matchReg)
                        if (pid && pid[0]) {
                            let doc = await mongodbHandle.playerDao.findOne({ _id: ObjectId(pid[0]) })
                            if (doc) {
                                rank.push({ userId: pid[0], damage, username: doc.playerData.playerName })
                            }
                        }
                    }
                    rank = rank.sort((a, b) => {
                        return b.damage - a.damage
                    })
                    for (let i = 0; i < rank.length; i++) {
                        let data = rank[i];
                        let reward, treasure
                        if (i <= 2) {
                            reward = worldBossReward[i]
                            treasure = {tID: utils.getOneFromArray(treasureReward), treasure: {lvl: 1, quality: Math.floor(Math.random() * 3) + 2}}
                        } else {
                            reward = worldBossReward[3]
                            treasure = {tID: utils.getOneFromArray(treasureReward), treasure: {lvl: 1, quality: Math.floor(Math.random() * 1) + 2}}
                        }
                        mongodbHandle.mailDao.newAndSave(data.userId, `奇遇Boss挑战排名第${i + 1}`, reward, [treasure])

                    }
                }
            }
        }
    }
}

let worldBossHandle = new WorldBossHandle()
export default worldBossHandle